<!--
 * @toLastEditors: yuSeen
 * @toLastEditTime: 2021-12-21 22:13:13
-->
<template>
    <div class="swiper" @mouseenter="showNav = true" @mouseleave="showNav = false">
        <!-- 每项 -->
        <div class="item" v-for="(item, index) in list" :key="index" :style="[item.style]" @click="itemClick(item)">
            <img :src="item.imageUrl" />
            <span class="tag" :style="{ backgroundColor: item.titleColor }">{{ item.typeTitle }}</span>
        </div>
        <!-- 导航 -->
        <div class="navBox" v-show="showNav">
            <div class="nav" @click="current = lastIndex">
                <svgIcon name="back" size="16" fill="#fff" hover></svgIcon>
            </div>
            <div class="nav" @click="current = nextIndex">
                <svgIcon name="back" size="16" fill="#fff" hover class="next"></svgIcon>
            </div>
        </div>
    </div>
    <!-- 分页指示器 -->
    <div class="pagination flex-c-c">
        <span v-for="i in end + 1" :key="i" class="dotItem" :class="{ 'actived': current === i - 1 }" @mouseenter="current = i - 1"></span>
    </div>
</template>

<script lang='ts' setup>
import type { IBanner } from '@/service/api/recommendMusic/types'
import { computed, ref, watch } from 'vue';
import { cloneDeep } from 'lodash'

const props = defineProps<{
    list: IBanner
}>()

// 列表最后一项的索引
const end = computed(() => props.list.length - 1)

// 上一张图片的索引
const lastIndex = computed(() => {
    if (current.value === 0) return end.value
    return current.value - 1
})

// 下一张图片的索引
const nextIndex = computed(() => {
    if (current.value === end.value) return 0
    return current.value + 1
})

// 替换数据，先计算好样式再渲染，避免在渲染时计算样式
const replaceList = () => {
    const newList = cloneDeep(props.list)
    for (let i = 0; i <= end.value; i++) {
        newList[i].style = getStyle(i)
    }
    return newList
}

// 当前索引
const current = ref(0)
// 轮播列表
const list = ref<IBanner>([])

// 监听轮播列表变化
watch(() => props.list, () => list.value = replaceList())
// 监听当前索引变化，计算列表样式
watch(() => current.value, () => list.value = replaceList())

// 计算每一项的样式
const getStyle = (index: number) => {
    const getTranslate = () => {
        if (index === nextIndex.value) {
            return 160
        }
        if (index === lastIndex.value) {
            return -160
        }
        return 0
    }
    const getIndex = () => {
        if (current.value === index) return 10
        if (index === nextIndex.value || index === lastIndex.value) return 5
        return 1
    }
    const getOpacity = () => {
        if (current.value === index) return 'visible'
        if (index === nextIndex.value || index === lastIndex.value) return 'visible'
        return 'hidden'
    }
    const style = {
        zIndex: getIndex(),
        visibility: getOpacity(),
        width: index === current.value ? '540px' : '430px',
        transform: `translateX(${getTranslate()}px)`
    }
    return style
}

// 是否展示左右箭头
const showNav = ref(false)

// 轮播图点击
const itemClick = (item: IBanner[0]) => {
}

// 自动播放， 每7s切换下一张
const autoPlay = setInterval(() => current.value = nextIndex.value, 7000)
</script>

<style scoped lang='scss'>
.swiper {
    @apply relative flex items-center justify-center h-60 min-h-60 cursor-pointer;
    width: 750px;
}
.item {
    position: absolute;
    transition: all 0.3s linear;
    transform: translateZ(0);
    border-radius: 7px !important;
    overflow: hidden;
    img {
        width: 540px;
        
    }
    .tag {
        position: absolute;
        right: 0;
        bottom: 0;
        height: 22px;
        line-height: 22px;
        padding: 0 13px;
        color: #fff;
        font-size: 10px;
        opacity: 0.9;
        border-top-left-radius: 8px;
    }
}
.navBox {
    @apply absolute flex justify-between items-center w-full h-full px-6;
    .nav {
        @apply flex justify-center items-center bg-black bg-opacity-30 rounded-full;
        width: 30px;
        height: 30px;
        z-index: 18;
    }
    .next {
        transform: rotate(-180deg);
    }
}
.pagination {
    .dotItem {
        @apply w-2 h-2 rounded-full bg-gray-300 bg-opacity-30 mr-2 cursor-pointer;
    }
    .actived {
        background-color: $theme-color;
    }
}
</style>
